#include "QtAV/Filter.h"
#include "private/Filter_p.h"
#include "QtAV/Statistics.h"
#include "QtAV/FilterManager.h"
#include "QtAV/AVOutput.h"
#include "QtAV/AVPlayer.h"

namespace QtAV {

void safeReleaseFilter(Filter **ppFilter)
{
    if (!ppFilter || !*ppFilter) {
        qWarning("filter to release is null!");
        return;
    }
    FilterManager::instance().releaseFilter(*ppFilter);
    *ppFilter = 0;
}

Filter::Filter()
{}

Filter::Filter(FilterPrivate &d)
    :DPTR_INIT(&d)
{

}

Filter::~Filter()
{
}

//copy qpainter if context nut null
void Filter::process(FilterContext *&context, Statistics *statistics, QByteArray* data)
{
    DPTR_D(Filter);    
    if (!d.context) {
        d.context = FilterContext::create(contextType());
        d.context->video_width = statistics->video_only.width;
        d.context->video_height = statistics->video_only.height;
    }
    // TODO: reduce mem allocation
    if (!context || context->type() != contextType()) {
        if (context) {
            delete context;
        }
        context = FilterContext::create(contextType());
        context->video_width = statistics->video_only.width;
        context->video_height = statistics->video_only.height;
    }
    // share common data
    d.context->shareFrom(context);
    d.context->initializeOnData(data);
    context->shareFrom(d.context);
    d.statistics = statistics;
    process();
}

void Filter::setEnabled(bool enabled)
{
    DPTR_D(Filter);
    d.enabled = enabled;
}

bool Filter::isEnabled() const
{
    DPTR_D(const Filter);
    return d.enabled;
}

FilterContext* Filter::context()
{
    DPTR_D(Filter);
    if (!d.context) {
        d.context = FilterContext::create(contextType());
    }
    return d.context;
}

FilterContext::Type Filter::contextType() const
{
    return FilterContext::None;
}

/*TODO: move to AVOutput.cpp to reduce dependency?*/
bool Filter::installTo(AVOutput *output)
{
    return output->installFilter(this);
}

/*TODO: move to AVPlayer.cpp to reduce dependency?*/
bool Filter::installToAudioThread(AVPlayer *player)
{
    return player->installAudioFilter(this);
}

bool Filter::installToVideoThread(AVPlayer *player)
{
    return player->installVideoFilter(this);
}

bool Filter::uninstall()
{
    return FilterManager::instance().uninstallFilter(this);
}

} //namespace QtAV
